import { Request, Response } from 'express';
import { validationResult } from 'express-validator';
import { ArticleService } from '../services/article.service';
import { ResponseUtil } from '../utils/response';
import { UserService } from '../services/user.service';

// 定义 AuthenticatedRequest 接口
interface AuthenticatedRequest extends Request {
    user?: {
        userId: number;
        account: string;
    };
}

export class ArticleController {
    private static articleControllerInstance: ArticleController;
    private articleService: ArticleService;
    private userService: UserService;

    private constructor() {
        this.articleService = ArticleService.getInstance();
        this.userService = new UserService();
        
        // 绑定方法以保持正确的 this 上下文
        this.createArticle = this.createArticle.bind(this);
        this.getArticleById = this.getArticleById.bind(this);
        this.updateArticle = this.updateArticle.bind(this);
        this.deleteArticle = this.deleteArticle.bind(this);
        this.getArticlesByAuthor = this.getArticlesByAuthor.bind(this);
        this.getPublicArticles = this.getPublicArticles.bind(this);
        this.toggleLike = this.toggleLike.bind(this);
    }

    public static getInstance(): ArticleController {
        if (!ArticleController.articleControllerInstance) {
            ArticleController.articleControllerInstance = new ArticleController();
        }
        return ArticleController.articleControllerInstance;
    }

    // 创建新文章，验证作者存在性并保存文章信息
    public async createArticle(req: AuthenticatedRequest, res: Response) {
        try {
            const errors = validationResult(req);
            if (!errors.isEmpty()) {
                return ResponseUtil.error(res, '参数错误', -1);
            }

            const { title, content, isPublic = true } = req.body;
            const authorId = req.user!.userId;

            const article = await this.articleService.createArticle({
                title,
                content,
                isPublic,
                authorId
            });

            return ResponseUtil.success(res, article, '文章创建成功');
        } catch (error) {
            console.error('创建文章失败:', error);
            return ResponseUtil.error(res, '创建文章失败', -1);
        }
    }

    // 根据ID获取文章详情，包括作者信息
    public async getArticleById(req: Request, res: Response) {
        try {
            const id = parseInt(req.params.id);
            if (isNaN(id)) {
                return ResponseUtil.error(res, '无效的文章ID', -1);
            }

            const article = await this.articleService.getArticleById(id);
            if (!article) {
                return ResponseUtil.error(res, '文章不存在', -1);
            }

            // 增加浏览量
            await this.articleService.incrementViewCount(id);

            return ResponseUtil.success(res, article, '获取文章成功');
        } catch (error) {
            console.error('获取文章失败:', error);
            return ResponseUtil.error(res, '获取文章失败', -1);
        }
    }

    // 更新文章信息，仅允许作者修改自己的文章
    public async updateArticle(req: AuthenticatedRequest, res: Response) {
        try {
            const errors = validationResult(req);
            if (!errors.isEmpty()) {
                return ResponseUtil.error(res, '参数错误', -1);
            }

            const id = parseInt(req.params.id);
            if (isNaN(id)) {
                return ResponseUtil.error(res, '无效的文章ID', -1);
            }

            const { title, content, isPublic } = req.body;
            const authorId = req.user!.userId;

            const article = await this.articleService.updateArticle(id, {
                title,
                content,
                isPublic,
                authorId
            });

            if (!article) {
                return ResponseUtil.error(res, '文章不存在或您没有权限修改', -1);
            }

            return ResponseUtil.success(res, article, '文章更新成功');
        } catch (error) {
            console.error('更新文章失败:', error);
            return ResponseUtil.error(res, '更新文章失败', -1);
        }
    }

    // 删除文章，验证权限并处理相关点赞记录
    public async deleteArticle(req: AuthenticatedRequest, res: Response) {
        try {
            const id = parseInt(req.params.id);
            if (isNaN(id)) {
                return ResponseUtil.error(res, '无效的文章ID', -1);
            }

            const authorId = req.user!.userId;
            
            const result = await this.articleService.deleteArticle(id, authorId);

            if (!result.success) {
                return ResponseUtil.error(res, result.message || '文章不存在或您没有权限删除', -1);
            }

            return ResponseUtil.success(res, null, result.message || '文章删除成功');
        } catch (error) {
            console.error('删除文章失败:', error);
            return ResponseUtil.error(res, error instanceof Error ? error.message : '删除文章失败', -1);
        }
    }

    // 获取指定作者的文章列表，支持分页
    public async getArticlesByAuthor(req: Request, res: Response) {
        try {
            const authorId = parseInt(req.params.authorId);
            if (isNaN(authorId)) {
                return ResponseUtil.error(res, '无效的用户ID', -1);
            }

            // 检查用户是否存在
            try {
                await this.userService.getUserInfo(authorId);
            } catch (error) {
                return ResponseUtil.error(res, '用户不存在', -1);
            }

            const pageNo = parseInt(req.query.pageNo as string) || 1;
            const pageSize = parseInt(req.query.pageSize as string) || 10;

            const result = await this.articleService.getArticlesByAuthor(authorId, pageNo, pageSize);
            return ResponseUtil.success(res, result, '获取用户文章列表成功');
        } catch (error) {
            console.error('获取用户文章列表失败:', error);
            return ResponseUtil.error(res, '获取用户文章列表失败', -1);
        }
    }

    // 获取所有公开文章列表，支持分页
    public async getPublicArticles(req: Request, res: Response) {
        try {
            const pageNo = parseInt(req.query.pageNo as string) || 1;
            const pageSize = parseInt(req.query.pageSize as string) || 10;

            const result = await this.articleService.getPublicArticles(pageNo, pageSize);
            return ResponseUtil.success(res, result, '获取公开文章列表成功');
        } catch (error) {
            console.error('获取公开文章列表失败:', error);
            return ResponseUtil.error(res, '获取公开文章列表失败', -1);
        }
    }

    // 切换文章的点赞状态，处理点赞和取消点赞逻辑
    public async toggleLike(req: AuthenticatedRequest, res: Response) {
        try {
            const articleId = parseInt(req.params.id);
            if (isNaN(articleId)) {
                return ResponseUtil.error(res, '无效的文章ID', -1);
            }

            const userId = req.user!.userId;
            const { action } = req.body;

            if (action !== 'like' && action !== 'unlike') {
                return ResponseUtil.error(res, '无效的操作', -1);
            }

            const result = await this.articleService.toggleLike(
                articleId,
                userId,
                action === 'like'
            );

            if (!result.success) {
                return ResponseUtil.error(res, '文章不存在', -1);
            }

            // 处理点赞操作
            if (action === 'like') {
                return ResponseUtil.success(res, null, '点赞成功');
            } 
            // 处理取消点赞操作
            else {
                return ResponseUtil.success(res, null, '取消点赞成功');
            }
        } catch (error) {
            console.error('点赞操作失败:', error);
            return ResponseUtil.error(res, '点赞操作失败', -1);
        }
    }
} 